# services/user_service.py
import logging
from typing import Optional
from datetime import timedelta

from core.config import settings
from core.dependencies import get_redis_service
from db.models.users import UserDocument, UserCreate, UserResponse
from core.security import get_password_hash, create_access_token, authenticate_user, verify_password
from db.models.wx_friends import WxFriendsModel
from db.models.wx_user_model import WxUser, WxUserModel
from db.mysql.dao.users import UsersDAO
from db.mysql.users import Users
from services.wx_friends_service import create_rag_friends
from services.wx_user_service import create_rag_by_user_id
from utils.result import Result
from sqlalchemy.orm import Session
logger = logging.getLogger("app."+__name__)

class UserService:
    @staticmethod
    async def create_user(user_create: UserCreate, db: Optional[Session]) -> Result:
        """创建用户"""
        try:
            if user_create.phone_code != "1234":
                return Result.fail(code=400,msg="验证码错误")
            # redis_server = await get_redis_service()
            # code = await redis_server.get_phone_validate_code(user_create.phone)
            # if not code:
            #     return Result.fail(code=400,msg="验证码已过期")
            # if user_create.phone_code != code:
            #     return Result.fail(code=400,msg="验证码错误")
            dao = UsersDAO(db=db)

            # 检查用户名是否已存在
            existing_user = dao.get_user_by_username(user_create.username)
            if existing_user:
                return Result.fail(msg="Username already registered")

            # 创建新用户
            user_data = {
                "username": user_create.username,
                "tel": user_create.phone,
                "email": user_create.email,
                "hashed_password": get_password_hash(user_create.password),
                "is_active": True,
                "is_superuser": False,
                "is_verified": False                
            }

            db_user = dao.create_user(user_data)
            if not db_user:
                return Result.fail(msg="Failed to create user")

            # 返回安全的用户信息
            user_response = UserResponse(
                user_id=db_user.user_id,
                username=db_user.username,
                phone=db_user.tel,
                email=db_user.email,
                is_active=db_user.is_active,
                is_superuser=db_user.is_superuser,
                is_verified=db_user.is_verified,
                created_at=db_user.created_at
            )

            # 为新用户创建一个rag机器人和测试好友
            await create_rag_by_user_id(user_id=db_user.user_id, user_name=db_user.username)
            await create_rag_friends(device_id=f"rag_{db_user.username}")

            return Result.success(data=user_response, msg="User created successfully")
        except Exception as e:
            logger.exception("Failed to create user", e)
            return Result.fail(msg=f"Failed to create user: {str(e)}")

    @staticmethod
    async def delete_user(user_id:str):
        try:
            user_doc = await UserDocument.find_one(UserDocument.user_id==user_id)
            if not user_doc:
                return Result.fail(msg="User not found")
            await user_doc.delete()
            return Result.success(msg="User deleted successfully")
        except Exception as e:
            logger.exception(msg=f"Failed to delete user: {str(e)}")
            return Result.fail(msg=f"Failed to delete user: {str(e)}")

    @staticmethod
    async def login_user(username: str, password: str,db) -> Result:
        """用户登录"""
        try:
            # 创建 DAO 实例
            dao = UsersDAO(db=db)
            # 查找用户
            user = dao.get_user_by_username(username)
            # 验证用户和密码
            if not user or not verify_password(password, user.hashed_password):
                return Result.fail(msg="用户名密码错误")

            # 创建访问令牌
            access_token_expires = timedelta(minutes=settings.ACCESS_TOKEN_EXPIRE_MINUTES)
            access_token = create_access_token(
                data={"sub": user.username}, expires_delta=access_token_expires
            )
            # 返回令牌和用户信息
            user_response = UserResponse(
                user_id=user.user_id,
                username=user.username,
                phone=user.tel,
                email=user.email,
                is_active=user.is_active,
                is_superuser=user.is_superuser,
                is_verified=user.is_verified,
                created_at=user.created_at,
                role="super_admin" if user.is_superuser else "user",
                tel=user.tel
            )

            return Result.success(
                data={
                    "access_token": access_token,
                    "token_type": "bearer",
                    "user": user_response
                },
                msg="Login successful"
            )
        except Exception as e:
            logger.error("Login failed", e)
            return Result.fail(msg=f"Login failed: {str(e)}")

    @staticmethod
    async def get_user_by_id(user_id: str, db: Session) -> Result:
        """根据ID获取用户 (MySQL 版本)"""
        try:
            # 创建 DAO 实例
            dao = UsersDAO(db=db)
            # 查找用户
            user = dao.get_user_by_user_id(user_id)
            if not user:
                return Result.fail(msg="User not found")

            # 构造响应
            user_response = UserResponse(
                user_id=user.user_id,
                username=user.username,
                email=user.email,
                phone=user.tel,
                is_active=user.is_active,
                is_superuser=user.is_superuser,
                is_verified=user.is_verified,
                created_at=user.created_at
            )

            return Result.success(data=user_response)
        except Exception as e:
            return Result.fail(msg=f"Failed to get user: {str(e)}")

    @staticmethod
    async def get_current_user_info(current_user: UserDocument) -> Result:
        """获取当前用户信息"""
        try:
            user_response = UserResponse(
                user_id=current_user.user_id,
                username=current_user.username,
                email=current_user.email,
                is_active=current_user.is_active,
                is_superuser=current_user.is_superuser,
                is_verified=current_user.is_verified,
                created_at=current_user.created_at,
                role="super_admin" if current_user.is_superuser else "user",
                tel=current_user.tel
            )

            return Result.success(data=user_response)
        except Exception as e:
            return Result.fail(msg=f"Failed to get user info: {str(e)}")

    @staticmethod
    async def get_users_list(skip: int = 0, limit: int = 100, username: Optional[str] = None,
                             db: Session = None) -> Result:
        """获取用户列表 (MySQL 版本)"""
        try:
            # 创建 DAO 实例
            dao = UsersDAO(db=db)

            # 查询用户列表
            if username:
                # 如果有用户名筛选条件
                users = dao.db.query(Users).filter(Users.username.like(f"%{username}%")).offset(skip).limit(limit).all()
                total_count = dao.db.query(Users).filter(Users.username.like(f"%{username}%")).count()
            else:
                # 获取所有用户
                users = dao.get_all_users(skip, limit)
                total_count = dao.db.query(Users).count()

            # 转换为响应格式
            user_responses = []
            for user in users:
                user_response = UserResponse(
                    user_id=user.user_id,
                    username=user.username,
                    email=user.email,
                    is_active=user.is_active,
                    is_superuser=user.is_superuser,
                    is_verified=user.is_verified,
                    created_at=user.created_at,
                    tel=user.tel,
                )
                user_responses.append(user_response)

            return Result.success(
                data={
                    "users": user_responses,
                    "total": total_count,
                    "skip": skip,
                    "limit": limit
                },
                msg="Users list retrieved successfully"
            )
        except Exception as e:
            logger.exception(msg=f"Failed to get users list: {str(e)}")
            return Result.fail(msg=f"Failed to get users list: {str(e)}")


    @staticmethod
    async def get_wx_list_by_user_id(user_id: str):
        wx_users = await WxUserModel.find(WxUserModel.user_id == user_id).to_list()
        if wx_users:
            return Result.success(
                data=[
                    {
                        "auth_key": wx_user.auth_key,
                        "device_id": wx_user.device_id,
                        "expire_time": wx_user.expire_time,
                        "ip": wx_user.ip,
                        "nickname": wx_user.nickname,
                        "status": wx_user.status,
                        "user_id": wx_user.user_id,
                    }
                    for wx_user in wx_users
                ]
            )
        else:
            return Result.fail(code=400, msg="未找到用户").model_dump()